﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Services;
using System.Web.Script.Services;
using System.Configuration;
using Google.GData.YouTube;
using Google.YouTube;
using Google.GData.Extensions.MediaRss;
using BLL;
using Logic.BusinessLogic.SocialNetworks;
using System.Xml;
using System.Xml.Linq;
using SocialNetworks.Config;

/// <summary>
/// Summary description for WebsiteService
/// </summary>
[WebService(Namespace = "http://tempuri.org/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
// To allow this Web Service to be called from script, using ASP.NET AJAX, uncomment the following line. 
 [System.Web.Script.Services.ScriptService]
public class WebsiteService : System.Web.Services.WebService    {

    public WebsiteService () {

        //Uncomment the following line if using designed components 
        //InitializeComponent(); 
    }

    [WebMethod]
	[ScriptMethod(ResponseFormat = ResponseFormat.Json)]
    public string HelloWorld() {
        return "Hello World";
    }

	[WebMethod]
	[ScriptMethod(ResponseFormat = ResponseFormat.Json)]
	public void RemoveTrack(int trackID)
	{
		Logic.BusinessLogic.Stats.RemoveTrack(trackID, Authentication.CurrentUserID);
	}


	#region Video Uploading methods
	
	static string apiKey
	{ get { return ConfigurationManager.AppSettings["ytApiKey"]; } }
	static string appName
	{ get { return ConfigurationManager.AppSettings["ytAppName"]; } }

	//private static FormUploadToken GetFormUploadToken(string title, string category, string keywords, string description)
	//{
	//    var request = new YouTubeRequest(new YouTubeRequestSettings(appName, "", apiKey,);
	//    Video newVideo = new Video();
	//    newVideo.Title = title;
	//    newVideo.Tags.Add(new MediaCategory(category, YouTubeNameTable.CategorySchema));
	//    newVideo.Keywords = keywords;
	//    newVideo.Description = description;
	//    newVideo.YouTubeEntry.Private = false;
	//    //newVideo.Tags.Add(new MediaCategory("mydevtag, anotherdevtag",
	//    // YouTubeNameTable.DeveloperTagSchema));
	//    //newVideo.YouTubeEntry.Location = new GeoRssWhere(37, -122);
	//    //newVideo.YouTubeEntry.setYouTubeExtension("location", "Mountain View, CA");

	//    FormUploadToken token = request.CreateFormUploadToken(newVideo);
	//    return token;
	//}

	public class TokenResponse
	{
		public string Url;
		public string Token;
	}

	[WebMethod(EnableSession = true)]
	[ScriptMethod(ResponseFormat = ResponseFormat.Json)]
	public TokenResponse CreateVideo(int accountID, string title, string category, string keywords, string description, bool isFacebook, bool isTwitter)
	{

		TokenResponse response = new TokenResponse();
		BO.User user = Authentication.GetCurrentUser();
		BO.Account account = BLL.Accounts.GetByID(accountID);
		//Authenticate

		var api = new Social.YouTube.YouTubeApi(new YouTubeConfig { SessionToken = account.YtToken });
		var token = api.GetFormUploadToken(title, category, keywords, description);

		var snSelector = new Logic.BusinessLogic.SocialNetworks.SnSelector { IsFacebook = isFacebook, IsTwitter = isTwitter };

		var post = Logic.BusinessLogic.Posting.InsertVideoToDB(title, description, user.ID, accountID, snSelector);

		response.Url = string.Format("{0} ?{1}", token.Url, AppParams.URLs.YoutubeUploaderNextUrl(post.ID.ToString()));
		response.Token = token.Token;

		return response;
	}

	
	

	#endregion


	[WebMethod]
	public XmlDocument PostTimeLine(long postID)
	{
		var itemDailyStats = Logic.BusinessLogic.Stats.GetPostDailyStats(postID);
		itemDailyStats = itemDailyStats.OrderBy(s => s.Date).ToList();
		if (itemDailyStats.Count == 0)
		{
			var chartEmpty = new XElement("chart", new XElement("series"), new XElement("graphs", new XElement("graph")));
			var xdocEmpty = new XmlDocument();
			xdocEmpty.LoadXml(chartEmpty.ToString());
			return xdocEmpty;
		}

		var series = itemDailyStats.Select(item => new XElement("value", new XAttribute("xid", itemDailyStats.IndexOf(item)), item.Date.ToString("MM/dd")));
				

		#region for later
		//var messageType = itemDailyStats[0].PostedItem.PostedItemType;
		//switch (messageType)
		//{
		//    case BO.PostedItemsTypes.Status:
		//        break;
		//    case BO.PostedItemsTypes.Video:
		//    //get commentNum from fb,us,twitter.
		//    //get views
		//    case BO.PostedItemsTypes.BlogPost:
		//    //get commentNum from fb,us,twitter.
		//    //get views
		//    case BO.PostedItemsTypes.Event:
		//    //get commentNum from fb,us,twitter.
		//    //get views
		//    case BO.PostedItemsTypes.Photos:
		//    //get commentNum from fb,us,twitter.
		//    //get views
		//    default:
		//        break;
		//}
		#endregion

		var graphFbComments = itemDailyStats.Select(item => new XElement("value", new XAttribute("xid", itemDailyStats.IndexOf(item)), item.FbCommentNum));
		var graphTwReplys = itemDailyStats.Select(item => new XElement("value", new XAttribute("xid", itemDailyStats.IndexOf(item)), item.TwReplyNum));
		var graphRetweets = itemDailyStats.Select(item => new XElement("value", new XAttribute("xid", itemDailyStats.IndexOf(item)), item.TwRetweetNum));

		var graphs = new XElement("graphs"
			, new XElement("graph", graphFbComments, new XAttribute("gid", 0))
			, new XElement("graph", graphTwReplys, new XAttribute("gid", 1))
			, new XElement("graph", graphRetweets, new XAttribute("gid", 2))
			);
		var chart = new XElement("chart", new XElement("series", series), graphs);
		var xdoc = new XmlDocument();
		xdoc.LoadXml(chart.ToString());
		return xdoc;
	}

	/// <summary>
	/// This utility object makes sure the numbers displayed on the graph are not too long
	/// </summary>
	private class NumbersFormatter
	{
		
	}

	
	[WebMethod]
	public XmlDocument TracedAccountTimeLine(long traceID)
	{
		var traceDailyStats = Logic.BusinessLogic.Stats.GetTraceDailyStats(traceID, null);
		if (traceDailyStats.Count == 0)
		{
			var chartEmpty = new XElement("chart", new XElement("series"), new XElement("graphs", new XElement("graph")));
			var xdocEmpty = new XmlDocument();
			xdocEmpty.LoadXml(chartEmpty.ToString());
			return xdocEmpty;
		}

		var series = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.Date.ToString("MM/dd")));

		var graphFans = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.FanNum));
		

		var graphs = new XElement("graphs"
			, new XElement("graph", graphFans, new XAttribute("gid", 0)));

		var chart = new XElement("chart", new XElement("series", series), graphs);
		var xdoc = new XmlDocument();
		xdoc.LoadXml(chart.ToString());
		return xdoc;
	}

	[WebMethod]
	public XmlDocument AccountTimeLine(long ID)
	{
		var traceDailyStats = Logic.BusinessLogic.Stats.GetAccountDailyStats(ID);
		traceDailyStats = traceDailyStats.OrderBy(s => s.Date).ToList();
		if (traceDailyStats.Count == 0)
		{
			var chartEmpty = new XElement("chart", new XElement("series"), new XElement("graphs", new XElement("graph")));
			var xdocEmpty = new XmlDocument();
			xdocEmpty.LoadXml(chartEmpty.ToString());
			return xdocEmpty;
		}

		var series = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.Date.ToString("MM/dd")));

		var graphFans = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.FbPageFanNum));
		var graphFollowers = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.TwFollowersNum));

		var graphs = new XElement("graphs"
			, new XElement("graph", graphFans, new XAttribute("gid", 0))
			, new XElement("graph", graphFollowers, new XAttribute("gid",1))
			);

		var chart = new XElement("chart", new XElement("series", series), graphs);
		var xdoc = new XmlDocument();
		xdoc.LoadXml(chart.ToString());
		return xdoc;
	}

	[WebMethod]
	public XmlDocument MasterAccountTimeLine(int ID)
	{
		var traceDailyStats = Logic.BusinessLogic.Stats.GetMasterAccountDailyStats(ID);
		if (traceDailyStats.Count == 0)
		{
			var chartEmpty = new XElement("chart", new XElement("series"), new XElement("graphs", new XElement("graph")));
			var xdocEmpty = new XmlDocument();
			xdocEmpty.LoadXml(chartEmpty.ToString());
			return xdocEmpty;
		}

		var series = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.Date.ToString("MM/dd")));

		var graphFans = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.FbPageFanNum));
		var graphFollowers = traceDailyStats.Select(item => new XElement("value", new XAttribute("xid", traceDailyStats.IndexOf(item)), item.TwFollowersNum));

		var graphs = new XElement("graphs"
			, new XElement("graph", graphFans, new XAttribute("gid", 0))
			, new XElement("graph", graphFollowers, new XAttribute("gid", 1))
			);

		var chart = new XElement("chart", new XElement("series", series), graphs);
		var xdoc = new XmlDocument();
		xdoc.LoadXml(chart.ToString());
		return xdoc;
	}
}
